home *** CD-ROM | disk | FTP | other *** search
/ Software Vault: The Diamond Collection / The Diamond Collection (Software Vault)(Digital Impact).ISO / cdr44 / wgtrun.zip / RUN3.C < prev    next >
C/C++ Source or Header  |  1995-02-21  |  7KB  |  348 lines

  1. #include <wgt5.h>
  2. #include <math.h>
  3.  
  4. /*
  5.  
  6.  Same as run2.c, only the robot is partially transparent.
  7.  
  8. */
  9.  
  10. unsigned char shadowtable[256];    /* Shadow table */
  11. unsigned char *transparency_table; /* a 65536 byte table,
  12.                       allocated dynamically */
  13.  
  14. color pal[256];         /* The palette used for every graphic image */
  15. block sprites[200];     /* Array of images for the running robot */
  16.  
  17. block background;       /* Holds the background scrolling image */
  18. block work;             /* Page for constructing each frame */
  19.  
  20.  
  21. /* A structure which holds the scrolling values for each horizontal line */
  22. typedef struct
  23.  {
  24.   int x;                /* Current x value, shifted by 8 */
  25.   int increment;        /* fixed point increment */
  26.  } line_scroll;
  27. line_scroll lines[80];  /* 80 scrolling lines along the ground */
  28.  
  29. /* A simple sprite structure */
  30. typedef struct
  31.  {
  32.   int x;
  33.   int y;
  34.   int anm;              /* Sprite number */
  35.  } sprite;
  36. sprite people[5];
  37.  
  38.  
  39. int backx = 0;          /* X value for the scrolling rocks */
  40. int backinc;            /* X increment for scrolling rocks */
  41.  
  42.  
  43.  
  44.  
  45. /* Loads the graphics files, and allocates buffers */
  46. void load_graphics (void)
  47. {
  48.  work = wallocblock (320, 200);
  49.  /* Allocate a work buffer */
  50.  
  51.  wloadsprites (pal, "run.spr", sprites, 0, 199);
  52.  background = wloadgif ("street.gif", pal);
  53.  wsetpalette (0, 255, pal);
  54.  
  55.  transparency_table = (unsigned char *)malloc (65536);
  56. }
  57.  
  58.  
  59.  
  60. /* Frees the buffers and sprites */
  61. void free_graphics (void)
  62. {
  63.  free (transparency_table);
  64.  wfreesprites (sprites, 0, 199);
  65.  wfreeblock (background);
  66.  wfreeblock (work);
  67. }
  68.  
  69.  
  70. /* Set up the initial scrolling values */
  71. void init_lines (void)
  72. {
  73. int i;
  74. int inc;
  75.  
  76.  inc = 128;     /* slowest scrolling speed (128/256 of a pixel */
  77.  
  78.  backx = 0;     /* rocks x value */
  79.  backinc = inc; /* rocks same speed as the ground */
  80.  
  81.  for (i = 0; i < 80; i++)
  82.   {
  83.    lines[i].x = 0;              /* clear out the x value */
  84.    lines[i].increment = inc;    /* set the scroll speed */
  85.    inc += 32;                   /* Make the next row move faster */
  86.   }
  87.  
  88. }
  89.  
  90.  
  91.  
  92. /* Construct the background image */
  93. void animate_lines (void)
  94. {
  95. block source1, source2;
  96. block dest1, dest2;
  97. block origsource, origdest;
  98. int i;
  99. int x;
  100.  
  101.  wcopyscreen (0, 0, 319, 51, background, 0, 0, work);
  102.  /* Draw the moon stationary */
  103.  
  104.  
  105.  /* Scroll the rocks */
  106.  backx += backinc;
  107.  if (backx >= 81920)   /* 81920 is 320 << 8 */
  108.      backx -= 81920;
  109.  
  110.  x = backx >> 8;
  111.  
  112.  /* Copy the rocks */
  113.  wcopyscreen (x, 52, 319, 119, background, 0, 52, work);
  114.  if (x > 0)
  115.    wcopyscreen (0, 52, x-1, 119, background, 320 - x, 52, work);
  116.  
  117.  
  118.  origdest = abuf + 120 * 320;           /* First row to copy */
  119.  origsource = background + 120 * 320;   /* First row to copy */
  120.  
  121.  for (i = 0; i < 80; i++)
  122.   {
  123.    /* Scroll this line */
  124.    lines[i].x += lines[i].increment;
  125.    if (lines[i].x >= 81920)   /* 81920 is 320 << 8, wraps scroll around */
  126.       lines[i].x -= 81920;
  127.  
  128.    
  129.    x = lines[i].x >> 8;
  130.    /* Get the x coord */
  131.  
  132.    dest1 = origdest + i * 320;
  133.    dest2 = dest1 + (319 - x);
  134.    source1 = origsource + i * 320;
  135.    source2 = source1 + x;
  136.    
  137.    /* Copy the line in two steps */
  138.    memcpy (dest1, source2, 320 - x);
  139.    if (x > 0)
  140.     memcpy (dest2, source1, x + 1);
  141.    
  142.   }
  143.  
  144. }
  145.  
  146.  
  147.  
  148. /* Animates and displays the running man */
  149. void animate_man (void)
  150. {
  151.  people[0].anm++;
  152.  if (people[0].anm > 29)
  153.    people[0].anm = 0;
  154.  
  155.  wputblock_shade (people[0].x, 158, sprites[people[0].anm+30],
  156.         shadowtable, 1);
  157.  wputblock_shade (people[0].x, people[0].y, sprites[people[0].anm],
  158.         transparency_table, 2);
  159.  
  160. }
  161.  
  162.  
  163.  
  164.  
  165. void wcreate_shadow_table (color *palette)
  166. {
  167. float fr, fg, fb;
  168. long ir, ig, ib;
  169.  
  170. long absr, absg, absb;
  171.  
  172.  
  173. int r,g,b;
  174.  
  175. short col;
  176. short findcol;
  177.  
  178. unsigned long lowest;
  179. unsigned char bestfit;
  180. unsigned long coldif;
  181.  
  182.  for (col = 0; col < 256; col++)
  183.   {
  184.  
  185.    fr = (float)palette[col].r * (0.5);
  186.    fg = (float)palette[col].g * (0.5);
  187.    fb = (float)palette[col].b * (0.5);
  188.  
  189.    ir = fr;
  190.    ig = fg;
  191.    ib = fb;
  192.  
  193.    lowest = 655350;
  194.    for  (findcol = 0; findcol < 256; findcol++)
  195.     {
  196.       absr = abs ( (long)palette[findcol].r - ir);
  197.       absg = abs ( (long)palette[findcol].g - ig);
  198.       absb = abs ( (long)palette[findcol].b - ib);
  199.  
  200.       coldif = absr + absg + absb;
  201.       if  ((coldif < lowest) && (findcol != col))
  202.       {
  203.     lowest = coldif;
  204.     bestfit = findcol;
  205.       }
  206.     }
  207.    shadowtable[col] = bestfit;
  208.   }
  209.  
  210. }
  211.  
  212.  
  213. void wcreate_transparency_table (color *pal)
  214. {
  215. float lightlevel1;
  216. float lightlevel2;
  217. float fr, fg, fb;
  218. float fr2, fg2, fb2;
  219. long ir, ig, ib;
  220.  
  221. long absr, absg, absb;
  222.  
  223. short col, col2;
  224. short findcol;
  225.  
  226. unsigned long lowest;
  227. unsigned char bestfit;
  228. unsigned long coldif;
  229.  
  230.  
  231.  lightlevel1 = 0.5;     /* Percent of color 1 */
  232.  lightlevel2 = 0.5;     /* Percent of color 2 */
  233.  
  234.  /* Lightlevel1 and lightlevel2 must total to 1 */
  235.  
  236.  /* Transparency is created by taking two colors, multiplying the
  237.  RGB values by a percentage, and adding the RGB values together.  The
  238.  new color will contain a little bit of each oringal color. */
  239.  
  240.  
  241.  /* For each of the 256 colors, we can mix with any other color, therefore
  242.  we need a 256x256 table. */
  243.  
  244.  wtextcolor (15);
  245.  wtexttransparent (TEXTFGBG);
  246.  wgtprintf (0, 0, NULL, "Making transparency table...", col2);
  247.  
  248.  for (col2 = 0; col2 < 256; col2++)
  249.  {
  250.   for (col = 0; col < 256; col++)
  251.   {
  252.    fr = (float)pal[col].r * lightlevel1;
  253.    fg = (float)pal[col].g * lightlevel1;
  254.    fb = (float)pal[col].b * lightlevel1;
  255.  
  256.    fr2= (float)pal[col2].r * lightlevel2;
  257.    fg2= (float)pal[col2].g * lightlevel2;
  258.    fb2= (float)pal[col2].b * lightlevel2;
  259.  
  260.    ir = (fr + fr2);
  261.    ig = (fg + fg2);
  262.    ib = (fb + fb2);
  263.  
  264.    lowest = 655350;
  265.    for  (findcol = 0; findcol < 256; findcol++)
  266.     {
  267.       absr = abs ( (long)pal[findcol].r - ir) * 30;
  268.       absg = abs ( (long)pal[findcol].g - ig) * 59;
  269.       absb = abs ( (long)pal[findcol].b - ib) * 11;
  270.  
  271.       coldif = sqrt(absr*absr + absg*absg + absb*absb);
  272.       if  (coldif < lowest)
  273.       {
  274.     lowest = coldif;
  275.     bestfit = findcol;
  276.       }
  277.     }
  278.    transparency_table[col2 * 256L + col] = bestfit;
  279.   }
  280.  
  281.   wgtprintf (0, 8, NULL, "Color %03hi", col2);
  282.  }
  283. }
  284.  
  285.  
  286. int load_table (char *filename, block table, int size)
  287. {
  288. FILE *in;
  289.  
  290.  in = fopen (filename, "rb");
  291.  if (in == NULL)
  292.    return 0;
  293.  fread (table, size, 1, in);
  294.  fclose (in);
  295.  return 1;
  296. }
  297.  
  298.  
  299. void save_table (char *filename, block table, int size)
  300. {
  301. FILE *out;
  302.  
  303.  out = fopen (filename, "wb");
  304.  fwrite (table, size, 1, out);
  305.  fclose (out);
  306.  
  307. }
  308.  
  309.  
  310.  
  311.  
  312. void main (void)
  313. {
  314.  
  315.  vga256 ();
  316.  
  317.  load_graphics ();
  318.  
  319.  init_lines ();
  320.  
  321.  /* Set the position of the running man */
  322.  people[0].x = 120;
  323.  people[0].y = 50;
  324.  people[0].anm = 0;
  325.  
  326.  wcreate_shadow_table (pal);
  327.  
  328.  if (!load_table ("trans.dat", transparency_table, 65536))
  329.   {
  330.    wcreate_transparency_table (pal);
  331.    save_table ("trans.dat", transparency_table, 65536);
  332.   }
  333.  
  334.  
  335.  do { 
  336.   wsetscreen (work);
  337.   animate_lines ();
  338.   animate_man ();
  339.   wnormscreen ();
  340.   wretrace ();
  341.   wputblock (0, 0, work, 0);
  342.   } while (!kbhit ());
  343.  
  344.  free_graphics ();
  345.  wsetmode (3);
  346. }
  347.  
  348.